//! \file Behavior_TODO.cpp
//! \brief Implements the <code>fullsail_ai::fundamentals::Behavior</code> abstract class.
//! \author Jeremiah Blanchard with code from Cromwell D. Enage

#include <queue>
#include <stack>
#include "Behavior.h"
#include "../Structures/QueueList.h"

namespace fullsail_ai { namespace fundamentals {

	unsigned Behavior::createdCount = 0;
	unsigned Behavior::destroyedCount = 0;

	unsigned Behavior::getCreatedCount()
	{
		return createdCount;
	}

	unsigned Behavior::getDestroyedCount()
	{
		return destroyedCount;
	}

	Behavior::Behavior(char const* _description)
	{
		description = _description;
	}

	char const* Behavior::toString() const
	{
		return description;
	}

	bool Behavior::isLeaf() const
	{
		return false;
	}

	//! \todo
	//!   - Implement the <code>Behavior</code> methods.
	size_t Behavior::getChildCount() const
	{
		return children.size();
	}

	Behavior* Behavior::getChild( size_t index )
	{
		return children[index];
	}

	Behavior const* Behavior::getChild( size_t index ) const
	{
		return children[index];
	}

	void Behavior::addChild( Behavior* child )
	{
		child->parent = this;
		children.push_back(child);
		//createdCount++;
	}
	void Behavior::TraversePre(Behavior const*pNode, void (*dataFunction)(Behavior const*) ) const
	{
		dataFunction(pNode);
		for(size_t i = 0; i < pNode->getChildCount();i++)
		{
			TraversePre(pNode->getChild(i),dataFunction);
		}	
	}
	void Behavior::TraversePost(Behavior const*pNode, void (*dataFunction)(Behavior const*) ) const
	{
		for(size_t i = 0; i < pNode->getChildCount();i++)
		{
			TraversePost(pNode->getChild(i),dataFunction);
		}
		dataFunction(pNode);
	}
	void Behavior::breadthFirstTraverse( void (*dataFunction)(Behavior const*) ) const
	{

		QueueList<Behavior const*> Queue;
		Behavior const* pNode = NULL;
		Queue.enqueue(this);
		while(!Queue.isEmpty())
		{
			pNode = Queue.getFront();
			Queue.dequeue();
			dataFunction(pNode);
			for(size_t i = 0; i < pNode->getChildCount();i++)
				Queue.enqueue(pNode->getChild(i));
		}
	}

	void Behavior::preOrderTraverse( void (*dataFunction)(Behavior const*) ) const
	{
		TraversePre(this,dataFunction);
	}

	void Behavior::postOrderTraverse( void (*dataFunction)(Behavior const*) ) const
	{
		TraversePost(this,dataFunction);
	}

	bool Behavior::run( void (*dataFunction)(Behavior const*), Agent* agent )
	{
		return false;
	}



}}  // namespace fullsail_ai::fundamentals
